package com.gate.way.demo.client;

import io.netty.channel.ChannelOption;
import io.netty.handler.timeout.ReadTimeoutHandler;
import io.netty.handler.timeout.WriteTimeoutHandler;
import org.springframework.http.client.reactive.ReactorClientHttpConnector;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.reactive.function.client.WebClient;
import reactor.core.publisher.Mono;
import reactor.netty.http.client.HttpClient;
import reactor.netty.tcp.TcpClient;

import java.util.concurrent.TimeUnit;

/**
 * @author wangzhilong
 * @date 2021/3/19
 */
@RestController
@RequestMapping("web")
public class WebClientController {


    public static void main(String[] args) {
        final Mono<String> mono = WebClient.create()
                //发送get请求
                .get()
                //请求路径
                .uri("http://jsonplaceholder.typicode.com/posts/1")
                //获取响应结果
                .retrieve()
                // 响应数据类型转换
                .bodyToMono(String.class);

        //测试阻塞获取数据
        //block()阻塞获取响应结果的方法，
        // subscribe()非阻塞异步结果订阅方法 结合webflux 实现异步IO
        System.out.println(mono.block());

    }

    private WebClient getWebClient(){
        TcpClient tcpClient = TcpClient
                .create()
                .option(ChannelOption.CONNECT_TIMEOUT_MILLIS, 5000)
                .doOnConnected(conn -> {
                    conn.addHandlerLast(new ReadTimeoutHandler(5000, TimeUnit.MILLISECONDS));
                    conn.addHandlerLast(new WriteTimeoutHandler(5000, TimeUnit.MILLISECONDS));
                });
        //HttpClient.from 此方式创建已经不推荐了
        //推荐使用HttpClient.create
        return WebClient.builder()
                .baseUrl("")
                .clientConnector(new ReactorClientHttpConnector(HttpClient.from(tcpClient)))
                .build();
        //推荐使用

    }

    /** MultiValueMap
     * 通过webclient 实现响应式异步请求，可以提高并发吞吐量
     * webclient 结合webflux 实现异步IO
     * @return
     */
    @GetMapping("g1")
    public Mono<String> test1(){
        return WebClient.create()
                //发送get请求
                .get()
                //请求路径
                .uri("http://jsonplaceholder.typicode.com/posts/1")
                //获取响应结果(只能获取HTTP报文中的body)
                //exchange()方法可以获取HTTP报文的状态码，headers cookies 等信息
                .retrieve()
                // 响应数据类型转换
                .bodyToMono(String.class)
//                .doOnNext()   //偷窥数据可以在此位置做监控
//                .onErrorResume()  //消费异常并装换成可读错误
                .log();
    }




}
